//
// Created by Administrator on 2017/10/10.
//

#include "MyRSA.h"
#include <cstddef>
#include <stdlib.h>
#include "Log.h"
#include "rsa.h"
#include "platform.h"



//#define PRIVATE_KEY "-----BEGIN PRIVATE KEY-----\nMIICdgIBADANBgkqhkiG9w0BAQEFAASCAmAwggJcAgEAAoGBAMq+dLwFJYNn3xmc\nbqT1zPLVrTf4jApvP7GkGQzmxQ2KboonB6RA7D0y6+Cyio6wmN9SEKDww+dFMwWp\nxVqXKMayy917VtdlIUXkH3Zu8e+FtYx7+UNN2ezo/ddTbGzQ6y2KfUay57xO1yUC\nzjL3GUq2341IyoutVPst6z/34aIxAgMBAAECgYANpIdCZ65Ai2rN1GL1oryp0osX\naxgxU48bqwksfxLfeGM71KiE+wFqlNSeiCUeuO9wh5sq2Ui1dUibpvLqx6UsqtwL\nzAZ02WLxl+jFtjs+H97PHXzfEwEXwzcpdFiJjBMi1ARvcdGWGXFlpjVEo03UukwD\nIs6c5AWGK2OK2ScPYQJBAP8Us63kPGlPr0R0s2SO/lpfd9UCfA9wfVbwmr/9jLxX\nC0Pqje8g7vlaR8jqteVd9/duPFqiKRruJw3yVdIsLu0CQQDLeXnoQIQBSZQi1qtp\n/07MFIsOhpfh3uJgEzwj3JiHA2vQ5AXXGvqrUJEWbMkU1tZIDJMPQsHaXAUunhxg\nzxPVAkBJShtuJRuubnS/SICarfMq6C84BqS6kumQZ0UvUJx1KNVVyDjLsjy3bFcf\nxUBKDLvIXeX9bIY+9JpICY7a+lLpAkEAk3/X03kROC2yaR7c29XrtR0fQMRozZ/Y\n0nSfIBAFsbnVKnRhl3FDTXT1+B+cFLM4Wrpi0KlABZ63Uvfi8nqqkQJAGWp/gbvG\n1kXTHp7hVfvw9fWlG6yC7Y7ah+16xueGQjs4gPVGoER6n9jLbOt6qkR2Ha1TioJn\nPFkcISJOerTceg==\n-----END PRIVATE KEY-----"
//#define PUBLICKEY "-----BEGIN PUBLIC KEY-----\nMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDKvnS8BSWDZ98ZnG6k9czy1a03\n+IwKbz+xpBkM5sUNim6KJwekQOw9MuvgsoqOsJjfUhCg8MPnRTMFqcValyjGssvd\ne1bXZSFF5B92bvHvhbWMe/lDTdns6P3XU2xs0Ostin1Gsue8TtclAs4y9xlKtt+N\nSMqLrVT7Les/9+GiMQIDAQAB\n-----END PUBLIC KEY-----"

#define PUBLICKEY "-----BEGIN PUBLIC KEY-----\nMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCvyO71pOAwFxZHKPmOnEuLr1wj\n02VBzyz7DYPNRfRCRPhoF+8o+XdOjRnIdssAyq104pAnd5BW3OPAfsbFSJIZ2rgA\n9HMkOhiE5gvUF964NiFldBYlSbUPs4oeB+jdxWgWdBQiyJc3m+bRPhM2t+nCGpgE\nF0wKTXxJmq/w9HhbkQIDAQAB\n-----END PUBLIC KEY-----"
#define PRIVATE_KEY "-"

#define  PADDING   RSA_PKCS1_PADDING          //填充方式
/**
 * 注意注意：不能用一种秘钥同时做加密解密。只能公钥加密+私钥解密 / 私钥加密+公钥解密
 *
 * 公钥存在客户端，私钥存在服务端
 * */

/**
 * 公钥加密
 * */
std::string MyRSA::encryptRSAbyPublickey(const std::string &data) {

    return nullptr;
}
/**
 * 公钥解密
 * */
std::string MyRSA::decryptRSAbyPublicKey(const std::string &data) {
    return nullptr;

}
/**
 * 私钥加密
 * */
std::string MyRSA::encryptRSAbyPrivateKey(const std::string &data) {
    return nullptr;
}
/**
 * 私钥解密
 * */
std::string MyRSA::decryptRSAbyPrivateKey(const std::string &data) {
    return nullptr;
}


#define KEY_LEN 128

#define RSA_N   "9292758453063D803DD603D5E777D788" \
                "8ED1D5BF35786190FA2F23EBC0848AEA" \
                "DDA92CA6C3D80B32C4D109BE0F36D6AE" \
                "7130B9CED7ACDF54CFC7555AC14EEBAB" \
                "93A89813FBF3C4F8066D2D800F7C38A8" \
                "1AE31942917403FF4946B0A83D3D3E05" \
                "EE57C6F5F5606FB5D4BC6CD34EE0801A" \
                "5E94BB77B07507233A0BC7BAC8F90F79"

#define RSA_E   "10001"

#define RSA_D   "24BF6185468786FDD303083D25E64EFC" \
                "66CA472BC44D253102F8B4A9D3BFA750" \
                "91386C0077937FE33FA3252D28855837" \
                "AE1B484A8A9A45F7EE8C0C634F99E8CD" \
                "DF79C5CE07EE72C7F123142198164234" \
                "CABB724CF78B8173B9F880FC86322407" \
                "AF1FEDFDDE2BEB674CA15F3E81A1521E" \
                "071513A1E85B5DFA031F21ECAE91A34D"

#define RSA_P   "C36D0EB7FCD285223CFB5AABA5BDA3D8" \
                "2C01CAD19EA484A87EA4377637E75500" \
                "FCB2005C5C7DD6EC4AC023CDA285D796" \
                "C3D9E75E1EFC42488BB4F1D13AC30A57"

#define RSA_Q   "C000DF51A7C77AE8D7C7370C1FF55B69" \
                "E211C2B9E5DB1ED0BF61D0D9899620F4" \
                "910E4168387E3C30AA1E00C339A79508" \
                "8452DD96A9A5EA5D9DCA68DA636032AF"

#define PT_LEN  24
#define RSA_PT  "\xAA\xBB\xCC\x03\x02\x01\x00\xFF\xFF\xFF\xFF\xFF" \
                "\x11\x22\x33\x0A\x0B\x0C\xCC\xDD\xDD\xDD\xDD\xDD"

static int myrand( void *rng_state, unsigned char *output, size_t len )
{
#if !defined(__OpenBSD__)
    size_t i;

    if( rng_state != NULL )
        rng_state  = NULL;

    for( i = 0; i < len; ++i )
        output[i] = rand();
#else
    if( rng_state != NULL )
        rng_state = NULL;

    arc4random_buf( output, len );
#endif /* !OpenBSD */

    return( 0 );
}

/*
 * Checkup routine
 */
unsigned char* encrypt()
{
#if defined(MBEDTLS_PKCS1_V15)
    int ret = 0;

    mbedtls_rsa_context rsa;
    unsigned char rsa_plaintext[PT_LEN];
    unsigned char rsa_ciphertext[KEY_LEN];

    mbedtls_mpi K;

    mbedtls_mpi_init( &K );
    mbedtls_rsa_init( &rsa, MBEDTLS_RSA_PKCS_V15, 0 );

    MBEDTLS_MPI_CHK( mbedtls_mpi_read_string( &K, 16, RSA_N  ) );
    MBEDTLS_MPI_CHK( mbedtls_rsa_import( &rsa, &K, NULL, NULL, NULL, NULL ) );
    MBEDTLS_MPI_CHK( mbedtls_mpi_read_string( &K, 16, RSA_P  ) );
    MBEDTLS_MPI_CHK( mbedtls_rsa_import( &rsa, NULL, &K, NULL, NULL, NULL ) );
    MBEDTLS_MPI_CHK( mbedtls_mpi_read_string( &K, 16, RSA_Q  ) );
    MBEDTLS_MPI_CHK( mbedtls_rsa_import( &rsa, NULL, NULL, &K, NULL, NULL ) );
    MBEDTLS_MPI_CHK( mbedtls_mpi_read_string( &K, 16, RSA_D  ) );
    MBEDTLS_MPI_CHK( mbedtls_rsa_import( &rsa, NULL, NULL, NULL, &K, NULL ) );
    MBEDTLS_MPI_CHK( mbedtls_mpi_read_string( &K, 16, RSA_E  ) );
    MBEDTLS_MPI_CHK( mbedtls_rsa_import( &rsa, NULL, NULL, NULL, NULL, &K ) );

    MBEDTLS_MPI_CHK( mbedtls_rsa_complete( &rsa ) );

    mbedtls_printf( "  RSA key validation: " );

    if( mbedtls_rsa_check_pubkey(  &rsa ) != 0 || mbedtls_rsa_check_privkey( &rsa ) != 0 )
    {
        mbedtls_printf( "failed\n" );
        ret = 1;
        goto cleanup;
    }

    mbedtls_printf( "passed\n  PKCS#1 encryption : " );

    memcpy( rsa_plaintext, RSA_PT, PT_LEN );

    if( mbedtls_rsa_pkcs1_encrypt( &rsa, myrand, NULL, MBEDTLS_RSA_PUBLIC, PT_LEN, rsa_plaintext, rsa_ciphertext ) != 0 )
    {
        mbedtls_printf( "failed\n" );
        ret = 1;
        goto cleanup;
    } else{
        mbedtls_printf("加密结果：%s",rsa_ciphertext);
    }

cleanup:
    mbedtls_mpi_free( &K );
    mbedtls_rsa_free( &rsa );

    return rsa_ciphertext;
#else
    return nullptr;
#endif
}
